<template>
  <component
    :is="buttonComponent"
    v-bind="buttonProps"
    :class="[
      buttonClasses,
      `button-${type}`,
      {
        'button-loading': loading,
        'button-disabled': disabled,
        'button-block': block,
        'button-round': round,
        'button-circle': circle,
        'button-plain': plain,
        'button-link': link,
        'button-text': text,
        [`button-${size}`]: size,
      },
    ]"
    @click="handleClick"
    @mouseenter="handleMouseEnter"
    @mouseleave="handleMouseLeave"
  >
    <!-- 加载状态遮罩 -->
    <div v-if="loading" class="button-loading-mask">
      <component :is="loadingIcon" class="animate-spin" />
    </div>

    <!-- 波纹效果 -->
    <div v-if="ripple && !disabled" ref="rippleRef" class="button-ripple"></div>

    <!-- 图标 -->
    <template #prefix>
      <component
        v-if="icon && !loading"
        :is="icon"
        :class="{ 'mr-2': $slots.default }"
      />
    </template>

    <!-- 默认插槽 -->
    <slot></slot>

    <!-- 前置内容 -->
    <template v-if="$slots.prepend" #prepend>
      <slot name="prepend" />
    </template>

    <!-- 后置内容 -->
    <template v-if="$slots.append" #append>
      <slot name="append" />
    </template>
  </component>
</template>

<script setup>
import { ref, computed } from "vue";
import { ElButton } from "element-plus";
import { Button as AButton } from "@arco-design/web-vue";

const props = defineProps({
  // 通用属性
  type: {
    type: String,
    default: "default",
    validator: (value) =>
      [
        "default",
        "primary",
        "success",
        "warning",
        "danger",
        "info",
        "text",
      ].includes(value),
  },
  size: {
    type: String,
    default: "default",
    validator: (value) => ["mini", "small", "default", "large"].includes(value),
  },
  icon: {
    type: [String, Object],
    default: "",
  },
  loading: {
    type: Boolean,
    default: false,
  },
  disabled: {
    type: Boolean,
    default: false,
  },
  round: {
    type: Boolean,
    default: false,
  },
  circle: {
    type: Boolean,
    default: false,
  },
  plain: {
    type: Boolean,
    default: false,
  },
  link: {
    type: Boolean,
    default: false,
  },
  text: {
    type: Boolean,
    default: false,
  },
  bg: {
    type: Boolean,
    default: false,
  },
  ripple: {
    type: Boolean,
    default: true,
  },
  autofocus: {
    type: Boolean,
    default: false,
  },
  nativeType: {
    type: String,
    default: "button",
    validator: (value) => ["button", "submit", "reset"].includes(value),
  },
  isAdmin: {
    type: Boolean,
    default: false,
  },
  block: {
    type: Boolean,
    default: false,
  },
  customClass: {
    type: String,
    default: "",
  },
});

const emit = defineEmits(["click", "mouseenter", "mouseleave"]);

const rippleRef = ref(null);
const isHovered = ref(false);

// 计算按钮组件
const buttonComponent = computed(() => (props.isAdmin ? AButton : ElButton));

// 计算加载图标组件
const loadingIcon = computed(() =>
  props.isAdmin ? "icon-loading" : "el-icon-loading",
);

// 计算按钮属性
const buttonProps = computed(() => {
  if (props.isAdmin) {
    return {
      type: props.type === "text" ? "text" : props.type,
      size: props.size,
      loading: props.loading,
      disabled: props.disabled,
      long: props.block,
      shape: props.circle ? "circle" : props.round ? "round" : "",
      status: props.type === "danger" ? "danger" : undefined,
    };
  } else {
    return {
      type: props.type,
      size: props.size,
      loading: props.loading,
      disabled: props.disabled,
      round: props.round,
      circle: props.circle,
      plain: props.plain,
      link: props.link,
      text: props.text,
      bg: props.bg,
      autofocus: props.autofocus,
      nativeType: props.nativeType,
    };
  }
});

// 计算按钮类名
const buttonClasses = computed(() => {
  return [
    "global-button",
    props.customClass,
    {
      "w-full": props.block && !props.isAdmin,
      "inline-flex items-center justify-center": true,
      "hover:brightness-110": !props.disabled && isHovered.value,
    },
  ];
});

// 处理点击事件
const handleClick = (event) => {
  if (!props.disabled && !props.loading) {
    emit("click", event);
    if (props.ripple) {
      createRippleEffect(event);
    }
  }
};

// 处理鼠标进入
const handleMouseEnter = (event) => {
  isHovered.value = true;
  emit("mouseenter", event);
};

// 处理鼠标离开
const handleMouseLeave = (event) => {
  isHovered.value = false;
  emit("mouseleave", event);
};

// 创建波纹效果
const createRippleEffect = (event) => {
  if (!rippleRef.value) return;

  const button = event.currentTarget;
  const ripple = rippleRef.value;
  const diameter = Math.max(button.clientWidth, button.clientHeight);
  const radius = diameter / 2;

  ripple.style.width = ripple.style.height = `${diameter}px`;
  ripple.style.left = `${event.offsetX - radius}px`;
  ripple.style.top = `${event.offsetY - radius}px`;
  ripple.classList.add("ripple-active");

  setTimeout(() => {
    ripple.classList.remove("ripple-active");
  }, 600);
};
</script>

<style lang="scss" scoped>
.global-button {
  @apply relative overflow-hidden transition-all duration-300;

  // 基础样式
  &.button-default {
    @apply bg-white text-gray-700 border border-gray-300;
  }

  &.button-primary {
    @apply bg-primary-600 text-white border-transparent;
  }

  &.button-success {
    @apply bg-success-600 text-white border-transparent;
  }

  &.button-warning {
    @apply bg-warning-600 text-white border-transparent;
  }

  &.button-danger {
    @apply bg-danger-600 text-white border-transparent;
  }

  &.button-info {
    @apply bg-gray-600 text-white border-transparent;
  }

  // 尺寸
  &.button-mini {
    @apply text-xs px-2 py-1;
  }

  &.button-small {
    @apply text-sm px-3 py-1.5;
  }

  &.button-large {
    @apply text-lg px-6 py-3;
  }

  // 变体样式
  &.button-plain {
    @apply bg-transparent border;

    &.button-primary {
      @apply border-primary-600 text-primary-600;
    }

    &.button-success {
      @apply border-success-600 text-success-600;
    }

    &.button-warning {
      @apply border-warning-600 text-warning-600;
    }

    &.button-danger {
      @apply border-danger-600 text-danger-600;
    }

    &.button-info {
      @apply border-gray-600 text-gray-600;
    }
  }

  &.button-link {
    @apply bg-transparent border-0 underline;
  }

  &.button-text {
    @apply bg-transparent border-0;
  }

  &.button-round {
    @apply rounded-full;
  }

  &.button-circle {
    @apply rounded-full aspect-square p-0;
    width: 2.5em;
    height: 2.5em;
  }

  // 状态样式
  &.button-disabled {
    @apply cursor-not-allowed opacity-60;
  }

  &.button-loading {
    @apply cursor-wait;
  }

  // 加载遮罩
  .button-loading-mask {
    @apply absolute inset-0 flex items-center justify-center bg-black bg-opacity-10;
  }

  // 波纹效果
  .button-ripple {
    @apply absolute rounded-full bg-white bg-opacity-30 scale-0 pointer-events-none;
    transition:
      transform 0.6s,
      opacity 0.6s;

    &.ripple-active {
      @apply scale-100 opacity-0;
      transition: 0s;
    }
  }
}

// 深度选择器样式
:deep(.el-button),
:deep(.arco-btn) {
  @apply m-0;
}
</style>
